package com.nulldev.util.java.swing.extSwing.legacy;

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.FlowLayout;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.LayoutManager;
import java.awt.Point;
import java.awt.Toolkit;
import java.awt.event.KeyEvent;
import java.awt.event.KeyListener;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
import java.awt.event.MouseMotionListener;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener;
import java.util.ArrayList;
import java.util.LinkedList;
import java.util.regex.Pattern;

import javax.swing.JFrame;
import javax.swing.JMenuBar;
import javax.swing.JPanel;
import javax.swing.JScrollPane;
import javax.swing.JSeparator;

import com.nulldev.util.java.swing.canvas.SmoothCanvas;
import com.nulldev.util.java.swing.extSwing.notifications.Notification;
import com.nulldev.util.logging.LoggerFactory;
import com.nulldev.util.other.FPSCounter;
import com.nulldev.util.other.Timer;
import com.nulldev.util.threading.legacy.ThreadExecutor;

@Deprecated
public class ePanel extends JFrame implements MouseListener, WindowListener, KeyListener, MouseMotionListener {
	
	private final JPanel safe;
	private final LinkedList<Notification> notes = new LinkedList<Notification>();
	private boolean darkMode;
	public ePanel() {
		this("");
		LoggerFactory.getLogger(true, true).warn("Unsupported operation.");
	}
	
	public void setDarkMode(final boolean enabled) {
		this.darkMode = enabled;
		super.setBackground((this.darkMode ? Color.DARK_GRAY : Color.WHITE));
	}
	
	public boolean isDarkMode() {
		return this.darkMode;
	}
	
	@Override
	public void setJMenuBar(final JMenuBar menubar) {
		safe.setBounds(0, 40, getWidth(), 40);
		this.safe.add(menubar, BorderLayout.SOUTH);
	}
	
	public ePanel(final String title) {
		super(title);
		setUndecorated(true);
		setBounds(100, 100, 950, 500);
		setLayout(new BorderLayout(0, 40));
		addMouseListener(this);
		addWindowListener(this);
		addKeyListener(this);
		addMouseMotionListener(this);
		this.safe = new JPanel(new BorderLayout(0, 20));
		safe.setBounds(0, 0, getWidth(), 40);
		final JSeparator sep = new JSeparator();
		safe.add(sep, BorderLayout.CENTER);
		add(safe, BorderLayout.NORTH);
		init();
		setDarkMode(true);
		setIconImage(Toolkit.getDefaultToolkit().getImage(ePanel.class.getResource("/com/nulldev/util/java/swing/extSwing/icon.png")));
	}
	
	public void init() {
		final FPSCounter fps = new FPSCounter();
		final eGraph graph = new eGraph(new ArrayList<Double>());
		graph.width = 150;
		graph.heigth = 50;
		graph.disableBottomText = true;
		graph.padding = 18;
		graph.setBounds(500, 500, 300, 150);
		fps.start();
		final String testText = "Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur. Excepteur sint occaecat cupidatat non proident, sunt in culpa qui officia deserunt mollit anim id est laborum.";
		final SmoothCanvas test = new SmoothCanvas() {
			
			int x = 50;
			int y = 50;
			int amount = 1;
			
			@Override
			public void drawCanvas(final Graphics2D g2d) {
				fps.callFPS();
				g2d.setColor((darkMode ? Color.DARK_GRAY : Color.WHITE));
				g2d.fillRect(0, 0, getWidth(), getHeight());
				
				g2d.setColor((darkMode ? Color.WHITE : Color.BLACK));
				//amount += 64;
				
				int y1 = 50;
				int yx = y1;//MathUtil.randInt(y1, y1 + 50);
				for (final String xf : testText.split(Pattern.quote("."))) {					
					g2d.drawString(xf + ".", 500, yx);
					yx += yx;
				}
				
				int y = getHeight() - 60;
				g2d.setColor((darkMode ? Color.WHITE : Color.GRAY));
				for (final Notification nf : (LinkedList<Notification>) notes.clone()) {
					g2d.setColor((darkMode ? Color.DARK_GRAY : Color.WHITE));
					g2d.fillRect(getWidth() - 220, y, 200, 40);
					g2d.setColor((darkMode ? Color.WHITE : Color.BLACK));
					g2d.drawRect(getWidth() - 220, y, 200, 40);
					g2d.drawString(nf.getText(), getWidth() - 210, y + 20);
					y -= 45;
				}
				g2d.setColor(Color.GRAY);
				g2d.fillRect(0, 0, 320, 200);
				g2d.setColor((darkMode ? Color.WHITE : Color.BLACK));
				g2d.drawString("Entites: " + amount, 5, 130);
				g2d.drawString("FPS: " + fps.getFPS(), 5, 145);
				g2d.drawString("Average: " + fps.getAVGFPS(), 5, 160);
				graph.addR((double) fps.getFPS());
				graph.paintComponent(g2d);
				graph.safeReset();
			}
		};
		test.setFPS(90L);
		test.vSync = false;
		final JScrollPane pane = new JScrollPane(test);
		add(pane, BorderLayout.CENTER);
	}
	
	@Override
	public void paint(final Graphics g) {
		super.paint(g);
		this.draw(g);
	}
	
	@Override
	public void paintAll(final Graphics g) {
		super.paintAll(g);
		this.draw(g);
	}
	
    @Override
	public void paintComponents(final Graphics g) {
    	super.paintComponents(g);
    	this.draw(g);
    }
    
    private boolean drawing;
    private void draw(final Graphics g) {
    	if (!drawing) {
    		this.drawI(g);
    	}
    }
    
    public void toggle() {
    	this.setVisible(!this.isVisible());
    }
    
    private void drawI(final Graphics g) {
    	this.drawing = true;
		final Graphics2D g2d = (Graphics2D) g;
		g.setColor((this.darkMode ? Color.DARK_GRAY : Color.WHITE));
		g.fillRect(-1, -1, getWidth(), 20);
		g.setColor(this.darkMode ? Color.WHITE : Color.BLACK);
		g.setFont(Font.decode("sansserif.plain"));
		if (getIconImage() != null) {
			g.drawImage(getIconImage(), 2, 2, 16, 16, null);
			g.drawString(getTitle(), 20, 15);
		}else {
			g.drawString(getTitle(), 5, 15);
		}
		g.drawRect(0, 0, getWidth(), 20);
		g.setColor(Color.RED);
		g.drawOval(getWidth() - 15, 5, 10, 10);
		g.fillOval(getWidth() - 15, 5, 10, 10);
		g.setFont(Font.decode("sansserif.plain").deriveFont(8f));
		g.setColor(Color.BLACK);
		g.drawString("X", getWidth() - 12, 14);
		g.setColor(new Color(44, 238, 144));
		g.drawOval(getWidth() - 30, 5, 10, 10);
		g.fillOval(getWidth() - 30, 5, 10, 10);
		g.setFont(Font.decode("sansserif.plain").deriveFont(8f));
		g.setColor(Color.BLACK);
		g.drawString("=", getWidth() - 28, 14);
		g.setColor(new Color(232, 247, 146));
		g.drawOval(getWidth() - 45, 5, 10, 10);
		g.fillOval(getWidth() - 45, 5, 10, 10);
		g.setFont(Font.decode("sansserif.plain").deriveFont(8f));
		g.setColor(Color.BLACK);
		g.drawString("¬", getWidth() - 43, 14);
		
//		int y = getHeight() - 20;
//		for (final Notfication nf : this.notes) {
//			g.setColor((this.darkMode ? Color.DARK_GRAY : Color.WHITE));
//			g.fillRect(getWidth() - 120, y, 100, 40);
//			y -= 45;
//		}
		this.drawing = false;
    }
	
	@Override
	public void setLayout(final LayoutManager manager) {
		if (manager instanceof BorderLayout) {
			final BorderLayout br = (BorderLayout) manager;
			br.setVgap(20);
		}else if (manager instanceof FlowLayout) {
			final FlowLayout fl = (FlowLayout) manager;
			fl.setVgap(20);
		}
		super.setLayout(manager);
	}

	@Override
	public void mouseClicked(MouseEvent e) {
	}

	@Override
	public void mousePressed(MouseEvent e) {
        initialClick = e.getPoint();
        getComponentAt(initialClick);
		if ((e.getX() > getWidth() - 15 && e.getX() < getWidth() - 5) && (e.getY() > 8 && e.getY() < 20)) {
			System.exit(-1);
		}else if ((e.getX() > getWidth() - 30 && e.getX() < getWidth() - 20) && (e.getY() > 8 && e.getY() < 20)) {
			if (this.isResizable()) {
				if (this.getExtendedState() == MAXIMIZED_BOTH) {
					this.setExtendedState(this.NORMAL);
				}else {
					this.setExtendedState(this.getExtendedState() | this.MAXIMIZED_BOTH);
				}
			}
		}else if ((e.getX() > getWidth() - 45 && e.getX() < getWidth() - 35) && (e.getY() > 8 && e.getY() < 20)) {
			this.setExtendedState(this.ICONIFIED);
		}
	}

	@Override
	public void mouseReleased(MouseEvent e) {
	}

	@Override
	public void mouseEntered(MouseEvent e) {
	}

	@Override
	public void mouseExited(MouseEvent e) {
	}

	@Override
	public void windowOpened(WindowEvent e) {
	}

	@Override
	public void windowClosing(WindowEvent e) {
	}

	@Override
	public void windowClosed(WindowEvent e) {
	}

	@Override
	public void windowIconified(WindowEvent e) {
		this.draw(this.getGraphics());
	}

	@Override
	public void windowDeiconified(WindowEvent e) {
		this.draw(this.getGraphics());
	}

	@Override
	public void windowActivated(WindowEvent e) {
	}

	@Override
	public void windowDeactivated(WindowEvent e) {
	}

	@Override
	public void keyTyped(KeyEvent e) {
	}

	@Override
	public void keyPressed(KeyEvent e) {
		if (e.isAltDown() && e.getKeyChar() == 'n') {
			final boolean res = !this.isDarkMode();
			ThreadExecutor.execute(new Runnable() {
				
				@Override
				public void run() {
					final Timer t = new Timer();
					t.setDelay(500L);
					t.start();
					final Notification nt = new Notification(res ? "Entered Dark Mode." : "Entered Light Mode.");
					notes.add(nt);
					while (t.ticks() < 2000) {
						try {
							Thread.sleep(500L);
						} catch (InterruptedException e) {
						}
					}
					t.pause();
					for (int i = 0; i < notes.size(); i++) {
						final Notification ns = notes.get(i);
						if (ns.equals(nt)) {
							notes.remove(i);
							break;
						}
					}
					
				}
			});
			this.setDarkMode(res);
			//this.graph.setForeground(this.darkMode ? Color.WHITE : Color.BLACK);
		}
	}

	@Override
	public void keyReleased(KeyEvent e) {
	}

	protected Point initialClick;
	@Override
	public void mouseDragged(MouseEvent e) {
		if ((e.getY() > 0 && e.getY() < 38)) {
			//setLocation((int) e.getXOnScreen() - 20, (int) e.getYOnScreen());
            int thisX = this.getLocation().x;
            int thisY = this.getLocation().y;

            // Determine how much the mouse moved since the initial click
            int xMoved = (thisX + e.getX()) - (thisX + initialClick.x);
            int yMoved = (thisY + e.getY()) - (thisY + initialClick.y);

            // Move window to this position
            int X = thisX + xMoved;
            int Y = thisY + yMoved;
            this.setLocation(X, Y);
		}
	}

	@Override
	public void mouseMoved(MouseEvent e) {
	}
}
